

#ifndef _UHY_LINEARSVM_H_
#define _UHY_LINEARSVM_H_
#include <stdio.h>

// Memory allocation
#define UHY_MALLOC( type , n ) ( type * )malloc( ( n ) * sizeof( type ) )

// SVM model parameters
struct parameter
{
	// Solve type	
	int solver_type;

	// Stop criteria
	double eps;	  

	// C value
	double C;

	// Weight
	int nr_weight;

	// Weight label
	int *weight_label;

	// Weight vector
	double* weight;

	// P value
	double p;
};

// SVM model
struct model
{
	// Model parameters
	struct parameter param;

	// Number of class
	int nr_class;

	// Number of feature
	int nr_feature;

	// Weight
	double *w;

	// Class label
	int *label;	

	// Bias
	double bias;
};

// SVM solve type
static const char *svm_solvetype[]=
{
	"L2R_LR", 
	"L2R_L2LOSS_SVC_DUAL",
	"L2R_L2LOSS_SVC", 
	"L2R_L1LOSS_SVC_DUAL",
	"MCSVM_CS",
	"L1R_L2LOSS_SVC", 
	"L1R_LR", "L2R_LR_DUAL",
	"", 
	"", 
	"",
	"L2R_L2LOSS_SVR",
	"L2R_L2LOSS_SVR_DUAL",
	"L2R_L1LOSS_SVR_DUAL",
	NULL
};

enum { 
	L2R_LR, 
	L2R_L2LOSS_SVC_DUAL,
	L2R_L2LOSS_SVC, 
	L2R_L1LOSS_SVC_DUAL,
	MCSVM_CS, 
	L1R_L2LOSS_SVC,
	L1R_LR, 
	L2R_LR_DUAL,
	L2R_L2LOSS_SVR = 11, 
	L2R_L2LOSS_SVR_DUAL,
	L2R_L1LOSS_SVR_DUAL }; 

/**
  * @brief								Load SVM model
  * @param			[in]			model_file_name - model name
  * @return							SVM model
  */
struct model *ReadSVMModel(
	const char *model_file_name );

/**
  * @brief								SVM predict value output
  * @param			[in]			model_ - input model
  * @param			[in]			x - input vector
  * @param			[inout]		dec_values - output 
  * @return							label
  */
float predict_values_new(
	const struct model *model_,
	float *x, 
	float *dec_values );

/**
  * @brief								SVM predict value output - old version
  * @param			[in]			model_ - input model
  * @param			[in]			x - input vector
  * @param			[inout]		prob_estimates - output 
  * @return							label
  */
int  predict_probability_old(
	const struct model *model_, 
	float *x, 
	float* prob_estimates );

/**
  * @brief								SVM predict value output
  * @param			[in]			model_ - input model
  * @param			[in]			x - input vector
  * @param			[inout]		prob_estimates - output 
  * @return							label
  */
float predict_probability_new(
	const struct model *model_, 
	float *x, 
	float* prob_estimates );

/**
  * @brief								Release SVM model
  * @param			[in]			model_ptr - model 
  * @return							SVM model
  */
void free_model_content(
	struct model *model_ptr );

/**
  * @brief								Release SVM model (whole structure)
  * @param			[in]			model_ptr_ptr - model name
  * @return							SVM model
  */
void free_and_destroy_model(
	struct model **model_ptr_ptr );

/**
  * @brief								SVM predict value output
  * @param			[in]			FirPreVal - input vector1
  * @param			[in]			SecPreVal - input vector2
  * @param			[in]			FirIdx - input index 1 
  * @param			[in]			SecIdx - input index 2 
  * @param			[in]			nClass - class number
  * @return							output label
  */
int MulClassfierJudgeExp( float *ProVal );

#endif /* _UHY_LINEARSVM_H_ */